package org.bing.engine.common.filter;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;

import org.bing.engine.common.logging.Log;
import org.bing.engine.common.logging.LogFactory;
import org.bing.engine.utility.helper.HostHelper;
import org.springframework.web.context.WebApplicationContext;
import org.springframework.web.context.support.WebApplicationContextUtils;

public class ServletContextSetting implements Filter {
    protected static final Log logger = LogFactory.getLog(ServletContextSetting.class);

    private ServletContextManager manager;
    private boolean first = true;

    public void init(FilterConfig filterConfig) throws ServletException {
        String name = filterConfig.getInitParameter("SpringBeanName");
        if (name == null) {
            name = "ServletContextManager";
        }
        ServletContext sc = filterConfig.getServletContext();
        WebApplicationContext context = WebApplicationContextUtils.getRequiredWebApplicationContext(sc);
        if (context != null) {
            try {
                manager = (ServletContextManager) context.getBean(name);
            } catch (Exception e) {
                logger.info("Fail to get servlet context manager!", e);
            }
        }
    }

    public void destroy() {
    }

    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        if (first) {
            first = false;
            HttpServletRequest req = (HttpServletRequest) request;
            String server = req.getServerName();
            if ("localhost".equalsIgnoreCase(server)) {
                server = HostHelper.getHostAddress();
            }
            int port = req.getServerPort();
            String path = req.getContextPath();
            ServletContextInfo info = new ServletContextInfo();
            info.setServerName(server);
            info.setServerPort(port);
            info.setContextPath(path);
            // do manage thing TODO impl do once
            doManage(info);
        }
        // do other filter
        chain.doFilter(request, response);
    }

    protected void doManage(ServletContextInfo info) {
        try {
            if (manager != null) {
                manager.manage(info);
            }
        } catch (Exception e) {
            logger.error("Fail to do servlet context manager!", e);
        }
    }
}
